package com.xwltz.web.exception;

import com.xwltz.core.exception.BaseException;
import com.xwltz.core.utils.StringUtils;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.lang.reflect.Method;

/**
 * @description BaseWebException
 * @information on version 1.0 be created by @xwltz at 2022/6/18 14:28
 */
@SuppressWarnings("unused")
public abstract class BaseWebException extends BaseException {

	public BaseWebException(String msg, Exception e) {
		super(msg, e);
	}

	public BaseWebException(String msg) {
		super(msg);
	}

	public String getExceptionMessage(Method method) {
		String exceptionName = getExceptionName();
		String message = exceptionName + ": " + getMessage();

		if (e == null) {
			LoggerFactory.getLogger(this.getClass()).error(message);
		} else {
			LoggerFactory.getLogger(this.getClass()).error(message, e);

			if (method != null) {
				RequestMapping mapping = method.getDeclaredAnnotation(RequestMapping.class);
				if (mapping != null && StringUtils.isNotEmpty(mapping.name()))
					message = String.format("%s [ %s ] %s: %s", exceptionName, mapping.name(), getMessage(), e.getMessage());
			}
		}

		return message;
	}

	protected Method getExceptionSource(Exception e) {
		Method controllerMethod = null;
		for (StackTraceElement element : e.getStackTrace()) {
			try {
				Class<?> c = Class.forName(element.getClassName());
				if (c.getDeclaredAnnotation(RestController.class) == null && c.getDeclaredAnnotation(Controller.class) == null)
					continue;

				for (Method m : c.getDeclaredMethods()) {
					if (m.getName().equals(element.getMethodName())) {
						controllerMethod = m;
						break;
					}
				}
			} catch (ClassNotFoundException ignored) {
			}
		}
		return controllerMethod;
	}
}
